package com.test.mybatis.session;

import com.test.mybatis.config.Configuration;
import com.test.mybatis.config.MappedStatement;
import com.test.mybatis.executor.Executor;
import com.test.mybatis.executor.SimpleExecutor;
import com.test.mybatis.proxy.MapperProxy;

import java.lang.reflect.Proxy;
import java.util.List;

public class DefaultSqlSession implements SqlSession{

    private final Configuration configuration;

    private Executor executor;

    public DefaultSqlSession(Configuration configuration) {
        super();
        this.configuration = configuration;
        executor = new SimpleExecutor(configuration);
    }

    public <T> T selectOne(String statement, Object parameter) {
        List<T> selectList = this.selectList(statement, parameter);
        if (selectList == null || selectList.size() == 0) {
            return null;
        }
        if (selectList.size() == 1) {
            return selectList.get(0);
        }else {
            throw new RuntimeException("too many result");
        }
    }

    public <T> List<T> selectList(String statement, Object parameter){
        MappedStatement ms = configuration.getMappedStatement().get(statement);
        // 我们的查询方法最终还是交给了Executor去执行，Executor里面封装了JDBC操作，传入参数包含了sql语句和参数
        return executor.query(ms, parameter);
    }

    public <T> T getMapper(Class<T> type){
        // 通过动态代理生成一个实现类，我们重点关注，动态代理实现，他是一个InvocationHandler
        // 传入参数是this，就是sqlSession的一个实例
        MapperProxy mp = new MapperProxy(this);
        // 给我一个接口，还你一个实现类
        return (T) Proxy.newProxyInstance(type.getClassLoader(), new Class[]{type}, mp);
    }
}
